﻿using FFmpegInterop;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.InteropServices.WindowsRuntime;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
using Windows.ApplicationModel.Core;
using Windows.Foundation;
using Windows.Foundation.Collections;
using Windows.Graphics.Display;
using Windows.Media.Core;
using Windows.System.Display;
using Windows.UI.Core;
using Windows.UI.Popups;
using Windows.UI.ViewManagement;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using Windows.UI.Xaml.Controls.Primitives;
using Windows.UI.Xaml.Data;
using Windows.UI.Xaml.Input;
using Windows.UI.Xaml.Media;
using Windows.UI.Xaml.Navigation;
using Windows.Web.Http;
using Windows.Storage;
using Windows.Storage.Streams;

// “空白页”项模板在 http://go.microsoft.com/fwlink/?LinkId=234238 上有介绍

namespace LikeBangumi
{
    /// <summary>
    /// 可用于自身或导航至 Frame 内部的空白页。
    /// </summary>
    public sealed partial class PlayerPage : Page
    {
        public PlayerPage()
        {
            this.InitializeComponent();
            NavigationCacheMode = NavigationCacheMode.Required;
            SystemNavigationManager.GetForCurrentView().BackRequested += PlayerPage_BackRequested;
        }

        string device = Windows.System.Profile.AnalyticsInfo.VersionInfo.DeviceFamily;
        private void PlayerPage_BackRequested(object sender, BackRequestedEventArgs e)
        {
            //e.Handled = true;
            mediaElement.IsFullWindow = false;
            mediaElement.Source = null;
            mediaElement.Stop();


        }

        protected override void OnNavigatedFrom(NavigationEventArgs e)
        {

        }
        private void GetSetting()
        {
            if (!settings.SettingContains("ForceAudio"))
            {
                settings.SetSettingValue("ForceAudio", false);
            }
            else
            {
                ForceAudio = (bool)settings.GetSettingValue("ForceAudio");
            }

            if (!settings.SettingContains("ForceVideo"))
            {
                settings.SetSettingValue("ForceVideo", false);
            }
            else
            {
                ForceAudio = (bool)settings.GetSettingValue("ForceVideo");
            }

            if (!settings.SettingContains("UseFFmpeg"))
            {
                settings.SetSettingValue("UseFFmpeg", false);
            }
            else
            {
                UseFFmpeg = (bool)settings.GetSettingValue("UseFFmpeg");
            }

        }
        protected override void OnNavigatedTo(NavigationEventArgs e)
        {
            if (settings.SettingContains("AutoFull"))
            {
                mediaElement.IsFullWindow = (bool)settings.GetSettingValue("AutoFull");
            }
            else
            {
                if (device == "Windows.Mobile")
                {
                    mediaElement.IsFullWindow = true;
                    settings.SetSettingValue("AutoFull", true);
                }
                else
                {
                    mediaElement.IsFullWindow = false;
                    settings.SetSettingValue("AutoFull", false);
                }
            }


            //if (device == "Windows.Mobile"||)
            //   {
            //      mediaElement.IsFullWindow = true;
            //   }

            // mediaElement.TransportControls.
            PlayModel par = e.Parameter as PlayModel;
            GetSetting();
            switch (par.type)
            {
                case BangumiType.Bilibili:
                    GetBiliUrl(par.info);
                    break;
                case BangumiType.Dilidili:
                    GetDiliUri(par.info);
                    break;
                case BangumiType.Tucao:

                    break;
                case BangumiType.Fengche:
                    GetFCUrl(par.info, par.part);
                    break;
                case BangumiType.Local:
                    PlayLoacl(par.info);
                    break;
                default:
                    break;
            }
        }
        private FFmpegInteropMSS FFmpegMSS;
        bool ForceAudio = false;
        bool ForceVideo = false;
        bool UseFFmpeg = false;
        SettingHelper settings = new SettingHelper();
        private async void GetBiliUrl(string info)
        {
            //http://interface.bilibili.com/playurl?platform=android&cid=5883400&quality=2&otype=json&appkey=422fd9d7289a1dd9&type=flv
            try
            {
                if (!settings.SettingContains("Bili-Type"))
                {
                    settings.SetSettingValue("Bili-Type", "mp4");
                }
                if (!settings.SettingContains("Bili-Qu"))
                {
                    settings.SetSettingValue("Bili-Qu", 3);
                }
                pr_Load.Visibility = Visibility.Visible;
                WebClientClass wc = new WebClientClass();
                string type = (string)settings.GetSettingValue("Bili-Type");
                int qu = (int)settings.GetSettingValue("Bili-Qu");
                string url = "http://interface.bilibili.com/playurl?platform=android&cid=" + info + "&quality=" + qu + "&otype=json&appkey=422fd9d7289a1dd9&type="+type;
                url += "&sign=" + BiliApiHelper.GetSign(url);

                string results = await wc.GetResults(new Uri(url));
                VideoUriModel model = JsonConvert.DeserializeObject<VideoUriModel>(results);
                List<VideoUriModel> model1 = JsonConvert.DeserializeObject<List<VideoUriModel>>(model.durl.ToString());
                PropertySet options = new PropertySet();
                if (type == "flv")
                {
                    await Task.Run(async () =>
                    {
                        FFmpegMSS = FFmpegInteropMSS.CreateFFmpegInteropMSSFromUri(model1[0].url, ForceAudio, ForceVideo, options);
                        MediaStreamSource mss = FFmpegMSS.GetMediaStreamSource();
                        //Pass MediaStreamSource to Media Element
                        await this.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>
                        {
                            mediaElement.SetMediaStreamSource(mss);
                        });
                    });
                }
                else
                {
                    mediaElement.Source = new Uri(model1[0].url);
                }

                //mediaElement.Source = new Uri(model1[0].url);
            }
            catch (Exception)
            {
                MessageDialog md = new MessageDialog("视频地址获取失败！", "错误");
                await md.ShowAsync();
            }
            finally
            {
                pr_Load.Visibility = Visibility.Collapsed;
            }
        }
        public async void GetDiliUri(string URL)
        {
            try
            {
                pr_Load.Visibility = Visibility.Visible;
                HttpClient hc = new HttpClient();
                hc.DefaultRequestHeaders.Add("user-agent", "Mozilla/5.0 (Linux; Android 5.0; SM-N9100 Build/LRX21V) AppleWebKit/537.36 (KHTML, like Gecko) Version/4.0 Chrome/37.0.0.0 Mobile Safari/537.36 MicroMessenger/6.0.2.56_r958800.520 NetType/WIFI");
                hc.DefaultRequestHeaders.Add("Referer", URL);
                HttpResponseMessage hr = await hc.GetAsync(new Uri(URL));
                hr.EnsureSuccessStatusCode();
                //   string content =await hr.Content.ReadAsStringAsync();
                var encodeResults = await hr.Content.ReadAsBufferAsync();
                string results = Encoding.UTF8.GetString(encodeResults.ToArray(), 0, encodeResults.ToArray().Length);
                Match mc = Regex.Match(results, @"<iframe.*?src=""(.*?)"".*?>", RegexOptions.Multiline);
                HttpResponseMessage hr1 = await hc.GetAsync(new Uri(mc.Groups[1].Value));
                hr1.EnsureSuccessStatusCode();
                var encodeResults2 = await hr1.Content.ReadAsBufferAsync();
                string a = Encoding.UTF8.GetString(encodeResults2.ToArray(), 0, encodeResults2.ToArray().Length);
                Match mc2 = Regex.Match(a, @"var vid=""(.*?)"";.*?var hd2=""(.*?)"";.*?var typ=""(.*?)"";.*?var sign=""(.*?)"";.*?var ulk=""(.*?)"";", RegexOptions.Singleline);

                Match mc3 = Regex.Match(a, @"&tmsign=(.*?)&ajax");
                string vid, hd2, typ, sign, ulk;
                vid = mc2.Groups[1].Value;
                hd2 = mc2.Groups[2].Value;
                typ = mc2.Groups[3].Value;
                sign = mc2.Groups[4].Value;
                ulk = mc2.Groups[5].Value;
                string url = "https://player.005.tv:60000/parse.php?h5url=null&type=" + typ + "&vid=" + vid + "&hd=" + 3 + "&sign=" + sign + "&tmsign=" + mc3.Groups[1].Value + "&ajax=1&userlink=" + ulk;
                HttpResponseMessage hr3 = await hc.GetAsync(new Uri(url));
                hr3.EnsureSuccessStatusCode();
                string c = await hr3.Content.ReadAsStringAsync();
                if (UseFFmpeg)
                {
                    await Task.Run(async () =>
                    {
                        FFmpegMSS = FFmpegInteropMSS.CreateFFmpegInteropMSSFromUri(c, ForceAudio, ForceVideo, new PropertySet());
                        MediaStreamSource mss = FFmpegMSS.GetMediaStreamSource();
                        //Pass MediaStreamSource to Media Element
                        await this.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>
                        {
                            mediaElement.SetMediaStreamSource(mss);
                        });
                    });

                }
                else
                {
                    mediaElement.Source = new Uri(c);
                }
                //mediaElement.Source = new Uri(c);
                //return c;
            }
            catch (Exception ex)
            {
                MessageDialog md = new MessageDialog("视频地址获取失败！" + ex.Message, "错误");
                await md.ShowAsync();
            }
            finally
            {
                pr_Load.Visibility = Visibility.Collapsed;
            }
        }
        private async void GetFCUrl(string URL, string part)
        {
           
            try
            {
                pr_Load.Visibility = Visibility.Visible;
                WebClientClass wc = new WebClientClass();
                string results = await wc.GetResults(new Uri(URL));
                //string jsUrl = "http://m.fengchedm.com" + Regex.Match(results, @"<script type=""text/javascript"" src=""(.*?)""></script><script>", RegexOptions.Multiline).Groups[1].Value;
                string jsresults = Regex.Unescape(Regex.Match(results, @"VideoListJson=.*?VideoListJson=(.*?)';",RegexOptions.Singleline).Groups[1].Value);
                //string infoResults = Regex.Match(jsresults,@"\['(.*?)',\[(.*?)\]\]",RegexOptions.Multiline).Groups[2].Value;
                List<string> str = new List<string>();
                foreach (Match item in Regex.Matches(jsresults, @"'(.*?)'"))
                {
                    //str.Add(item.Groups[1].Value.Split('$')[0]);
                    if (item.Groups[1].Value.Split('$')[0] == part)
                    {
                        str = item.Groups[1].Value.Split('$').ToList();
                    }
                }
                if (str[2] != "iqiyi" && str[2] != "qiyi")
                {
                    PropertySet options = new PropertySet();
                    // https://52dongm.duapp.com/play/newurl.php?type=bilibili&id=7582157&ctype=phone
                    // string url = string.Format("https://52dongm.duapp.com/play/newurl.php?type={0}&id={1}&ctype=phone", str[2], str[1]);

                    string url = "";
                    if (str[1].Length>20)
                    {
                        url = str[1];
                    }
                    else
                    {
                        url = string.Format("https://52dongm.duapp.com/play/newurl.php?type={0}&id={1}&ctype=phone", str[2], str[1]);
                    }
                    if (UseFFmpeg)
                    {
                        System.Net.Http.HttpClientHandler handler = new System.Net.Http.HttpClientHandler();
                        handler.AllowAutoRedirect = false;
                        System.Net.Http.HttpClient client = new System.Net.Http.HttpClient(handler);

                        System.Net.Http.HttpResponseMessage response = await client.GetAsync(url);

                        if (response.StatusCode == System.Net.HttpStatusCode.Redirect || response.StatusCode == System.Net.HttpStatusCode.MovedPermanently)
                        {
                            Uri redirectUri = response.Headers.Location;
                            url = redirectUri.AbsoluteUri;
                        }
                        await Task.Run(async () =>
                        {
                            FFmpegMSS = FFmpegInteropMSS.CreateFFmpegInteropMSSFromUri(url, ForceAudio, ForceVideo, options);
                            MediaStreamSource mss = FFmpegMSS.GetMediaStreamSource();
                            //Pass MediaStreamSource to Media Element
                            await this.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>
                            {
                                mediaElement.SetMediaStreamSource(mss);
                            });
                        });

                    }
                    else
                    {
                        mediaElement.Source = new Uri(url);
                    }

                    //mediaElement.Source = new Uri();
                }
                //var a=from x in str where x.
                //List<VideoUriModel> model1 = JsonConvert.DeserializeObject<List<VideoUriModel>>(model.durl.ToString());
                //mediaElement.Source = new Uri(model1[0].url);
            }
            catch (Exception)
            {
                MessageDialog md = new MessageDialog("视频地址获取失败！", "错误");
                await md.ShowAsync();
            }
            finally
            {
                pr_Load.Visibility = Visibility.Collapsed;
            }
        }

        private async void PlayLoacl(string path)
        {

            try
            {
                pr_Load.Visibility = Visibility.Collapsed;
                StorageFile file = await StorageFile.GetFileFromPathAsync(path);
                if (file == null)
                {
                    await new MessageDialog("视频文件读取失败").ShowAsync();
                    return;
                }
                if (UseFFmpeg)
                {
                    IRandomAccessStream readStream = await file.OpenAsync(FileAccessMode.Read);
                    FFmpegMSS = FFmpegInteropMSS.CreateFFmpegInteropMSSFromStream(readStream, ForceAudio, ForceVideo);
                    MediaStreamSource mss = FFmpegMSS.GetMediaStreamSource();
                    if (mss != null)
                    {
                        mediaElement.SetMediaStreamSource(mss);
                    }
                    else
                    {
                        await new MessageDialog("Cannot open media").ShowAsync();
                    }

                }
                else
                {
                    IRandomAccessStream readStream = await file.OpenAsync(FileAccessMode.Read);
                    // var stream = await file.OpenAsync(Windows.Storage.FileAccessMode.Read);
                    mediaElement.SetSource(readStream, file.ContentType);
                }
            }
            catch (Exception ex)
            {
                await new MessageDialog("视频文件读取失败"+ex.Message).ShowAsync();
            }

        }


        private async void Info_Click(object sender, RoutedEventArgs e)
        {
            //mediaElement.NaturalDuration.TimeSpan.Hours.ToString("00") + ":" + mediaElement.NaturalDuration.TimeSpan.Minutes.ToString("00") + ":" + mediaElement.NaturalDuration.TimeSpan.Seconds.ToString("00") + "\r\n缓冲进度：" + mediaElement.DownloadProgress.ToString("P")
            string info = string.Format("视频高度：{0}\r\n视频宽度：{1}\r\n视频长度：{2}\r\n缓冲进度:{3}", mediaElement.NaturalVideoHeight, mediaElement.NaturalVideoWidth, mediaElement.NaturalDuration.TimeSpan.Hours.ToString("00") + ":" + mediaElement.NaturalDuration.TimeSpan.Minutes.ToString("00") + ":" + mediaElement.NaturalDuration.TimeSpan.Seconds.ToString("00"), mediaElement.DownloadProgress.ToString("P"));
            await new MessageDialog(info, "视频信息").ShowAsync();

        }
    }
    public class VideoUriModel
    {
        public string format { get; set; }//视频类型

        public object durl { get; set; }//视频信息

        public string url { get; set; }//视频地址

        public object backup_url { get; set; }//视频备份地址
    }
    public class PlayModel
    {
        public BangumiType type { get; set; }
        public string info { get; set; }
        public string part { get; set; }
    }
}
